#include <gtest/gtest.h>
#include <string>
#include <memory>
#include <fstream>
#include <vector>

#include "jkutil/iniparser.h"

using namespace std;
using Util::IniParser;
class TestIniParser : public testing::Test
{
public:
    virtual void SetUp()
    {
        system("rm -f /tmp/none.ini");
        p = new IniParser(filename.c_str());
        p_err = new IniParser(none_filename.c_str());
    }
    virtual void TearDown()
    {
        if(p != nullptr)
        {
            p->set("WriteTest.key", 1);
            vector<int32_t> def_val = {0, 0, 1};
            p->set("WriteTest.array_key", def_val);
            delete p;
        }
    }
    Util::IniParser* p_err;
    Util::IniParser* p;
    std::string filename = "src/jkutil/test/usertest.ini";
    std::string none_filename = "/tmp/none.ini";
};

TEST_F(TestIniParser, get_int32)
{
    int32_t val = 0;
    int32_t def_val = 1;
    ASSERT_EQ(p->get("Single_Int.INT_POSITIVE", val, def_val, INT32_MIN, INT32_MAX), Util::IniParser::OK);
    EXPECT_EQ(val, 10);

    val = 0;
    ASSERT_EQ(p->get("Single_Int.INT_NEGATIVE", val, def_val, INT32_MIN, INT32_MAX), Util::IniParser::OK);
    EXPECT_EQ(val, -10);

    //invalid filename
    val = 0;
    ASSERT_EQ(p_err->get("Single_Int.INT_NEGATIVE", val, def_val, INT32_MIN, INT32_MAX), Util::IniParser::FILE_ERR);
    EXPECT_EQ(val, def_val);

    // invalid VALUE
    val = 0;
    ASSERT_EQ(p->get("Empty.ONLY_KEY", val, def_val, INT32_MIN, INT32_MAX), Util::IniParser::VALUE_TYPE_ERR);
    EXPECT_EQ(val, def_val);

    // invalid KEY
    val = 0;
    ASSERT_EQ(p->get("Single_Int.NO_SUCH_KEY", val, def_val, INT32_MIN, INT32_MAX), Util::IniParser::READ_ERR);
    EXPECT_EQ(val, def_val);

    // invalid SECTION
    val = 0;
    ASSERT_EQ(p->get("NO_SUCH_SECTION.NO_SUCH_KEY", val, def_val, INT32_MIN, INT32_MAX), Util::IniParser::READ_ERR);
    EXPECT_EQ(val, def_val);

    // test max
    val = 0;
    ASSERT_EQ(p->get("Single_Int.INT_POSITIVE", val, def_val, -5, 5), Util::IniParser::VALUE_RANGE_ERR);
    EXPECT_EQ(val, def_val);

    val = 0;
    ASSERT_EQ(p->get("Single_Int.MAX_INT32", val, def_val, INT32_MIN, INT32_MAX), Util::IniParser::OK);
    EXPECT_EQ(val, INT32_MAX);

    val = 0;
    ASSERT_EQ(p->get("Single_Int.MAX_INT64", val, def_val, INT32_MIN, INT32_MAX), Util::IniParser::VALUE_TYPE_ERR);
    EXPECT_EQ(val, def_val);

    // test min
    val = 0;
    ASSERT_EQ(p->get("Single_Int.INT_NEGATIVE", val, def_val, -5, 5), Util::IniParser::VALUE_RANGE_ERR);
    EXPECT_EQ(val, def_val);

    val = 0;
    ASSERT_EQ(p->get("Single_Int.MIN_INT32", val, def_val, INT32_MIN, INT32_MAX), Util::IniParser::OK);
    EXPECT_EQ(val, INT32_MIN);

    val = 0;
    ASSERT_EQ(p->get("Single_Int.MIN_INT64", val, def_val, INT32_MIN, INT32_MAX), Util::IniParser::VALUE_TYPE_ERR);
    EXPECT_EQ(val, def_val);

    //TYPE ERR
    val = 0;
    ASSERT_EQ(p->get("String.STRING_NORMAL", val, def_val, INT32_MIN, INT32_MAX), Util::IniParser::VALUE_TYPE_ERR);
    EXPECT_EQ(val, def_val);

    val = 0;
    ASSERT_EQ(p->get("Single_Double.DOUBLE_POSITIVE", val, def_val, INT32_MIN, INT32_MAX), Util::IniParser::VALUE_TYPE_ERR);
    EXPECT_EQ(val, def_val);
}
TEST_F(TestIniParser, get_int32_array)
{
    vector<int32_t> val;
    vector<int32_t> def_val = {1, 2, 3};
    ASSERT_EQ(p->get("Array_Int.A_INT_3", val, def_val, INT32_MIN, INT32_MAX), Util::IniParser::OK);
    EXPECT_EQ(val[0], -10);
    EXPECT_EQ(val[1], 0);
    EXPECT_EQ(val[2], 10);

    ASSERT_EQ(p->get("Array_Int.A_INT_3_BLANK", val, def_val, INT32_MIN, INT32_MAX), Util::IniParser::OK);
    EXPECT_EQ(val[0], -10);
    EXPECT_EQ(val[1], 0);
    EXPECT_EQ(val[2], 10);

    //invalid filename
    ASSERT_EQ(p_err->get("Single_Int.INT_NEGATIVE", val, def_val, INT32_MIN, INT32_MAX), Util::IniParser::FILE_ERR);
    EXPECT_EQ(val[0], def_val[0]);
    EXPECT_EQ(val[1], def_val[1]);
    EXPECT_EQ(val[2], def_val[2]);

    // invalid VALUE
    ASSERT_EQ(p->get("Empty.ONLY_KEY", val, def_val, INT32_MIN, INT32_MAX), Util::IniParser::INI_VECTOR_FORMAT_ERR);
    EXPECT_EQ(val[0], def_val[0]);
    EXPECT_EQ(val[1], def_val[1]);
    EXPECT_EQ(val[2], def_val[2]);

    // invalid KEY
    ASSERT_EQ(p->get("Array_Int.NO_SUCH_KEY", val, def_val, INT32_MIN, INT32_MAX), Util::IniParser::READ_ERR);
    EXPECT_EQ(val[0], def_val[0]);
    EXPECT_EQ(val[1], def_val[1]);
    EXPECT_EQ(val[2], def_val[2]);

    // invalid SECTION
    ASSERT_EQ(p->get("NO_SUCH_SECTION.NO_SUCH_KEY", val, def_val, INT32_MIN, INT32_MAX), Util::IniParser::READ_ERR);
    EXPECT_EQ(val[0], def_val[0]);
    EXPECT_EQ(val[1], def_val[1]);
    EXPECT_EQ(val[2], def_val[2]);

    // 读取元素数量超过默认值
    ASSERT_EQ(p->get("Array_Int.A_INT_4", val, def_val, INT32_MIN, INT32_MAX), Util::IniParser::DEFAULT_LEN_NOT_MACTH);
    EXPECT_EQ(val[0], 0);
    EXPECT_EQ(val[1], 1);
    EXPECT_EQ(val[2], 2);

    // 读取元素数量少于默认值
    ASSERT_EQ(p->get("Array_Int.A_INT_2", val, def_val, INT32_MIN, INT32_MAX), Util::IniParser::DEFAULT_LEN_NOT_MACTH);
    EXPECT_EQ(val[0], 0);
    EXPECT_EQ(val[1], 1);
    EXPECT_EQ(val[2], def_val[2]);

    // Vector格式不满足以'{}'为开始和结束
    ASSERT_EQ(p->get("Array_Int.A_INT_HALF", val, def_val, INT32_MIN, INT32_MAX), Util::IniParser::INI_VECTOR_FORMAT_ERR);
    EXPECT_EQ(val[0], def_val[0]);
    EXPECT_EQ(val[1], def_val[1]);
    EXPECT_EQ(val[2], def_val[2]);

    //test range
    ASSERT_EQ(p->get("Array_Int.A_INT_3", val, def_val, -5, 5), Util::IniParser::VALUE_RANGE_ERR);
    EXPECT_EQ(val[0], def_val[0]);
    EXPECT_EQ(val[1], 0);
    EXPECT_EQ(val[2], def_val[2]);

    ASSERT_EQ(p->get("Array_Int.A_INT32_3", val, def_val, INT32_MIN, INT32_MAX), Util::IniParser::OK);
    EXPECT_EQ(val[0], INT32_MAX);
    EXPECT_EQ(val[1], INT32_MIN);
    EXPECT_EQ(val[2], 2);

    ASSERT_EQ(p->get("Array_Int.A_INT64_3", val, def_val, INT32_MIN, INT32_MAX), Util::IniParser::VALUE_TYPE_ERR);
    EXPECT_EQ(val[0], def_val[0]);
    EXPECT_EQ(val[1], def_val[1]);
    EXPECT_EQ(val[2], 2);

    //test type err
    ASSERT_EQ(p->get("Array_String.A_STRING_3_NORMAL", val, def_val, INT32_MIN, INT32_MAX), Util::IniParser::VALUE_TYPE_ERR);
    EXPECT_EQ(val[0], def_val[0]);
    EXPECT_EQ(val[1], def_val[1]);
    EXPECT_EQ(val[2], def_val[2]);
}

TEST_F(TestIniParser, get_double)
{
    double val = 0;
    double def_val = 1.1;
    ASSERT_EQ(p->get("Single_Double.DOUBLE_POSITIVE", val, def_val, -DBL_MAX, DBL_MAX), Util::IniParser::OK);
    EXPECT_EQ(val, 10.1);

    val = 0;
    ASSERT_EQ(p->get("Single_Double.DOUBLE_NEGATIVE", val, def_val, -DBL_MAX, DBL_MAX), Util::IniParser::OK);
    EXPECT_EQ(val, -10.1);

    //invalid filename
    ASSERT_EQ(p_err->get("Single_Double.DOUBLE_NEGATIVE", val, def_val, -DBL_MAX, DBL_MAX), Util::IniParser::FILE_ERR);
    EXPECT_EQ(val, def_val);

    // invalid VALUE
    val = 0;
    ASSERT_EQ(p->get("Empty.ONLY_KEY", val, def_val, -DBL_MAX, DBL_MAX), Util::IniParser::VALUE_TYPE_ERR);
    EXPECT_EQ(val, def_val);

    // invalid KEY
    val = 0;
    ASSERT_EQ(p->get("Single_Double.NO_SUCH_KEY", val, def_val, -DBL_MAX, DBL_MAX), Util::IniParser::READ_ERR);
    EXPECT_EQ(val, def_val);

    // invalid SECTION
    val = 0;
    ASSERT_EQ(p->get("NO_SUCH_SECTION.NO_SUCH_KEY", val, def_val, -DBL_MAX, DBL_MAX), Util::IniParser::READ_ERR);
    EXPECT_EQ(val, def_val);

    // test max
    val = 0;
    ASSERT_EQ(p->get("Single_Double.DOUBLE_POSITIVE", val, def_val, -5.0, 5.0), Util::IniParser::VALUE_RANGE_ERR);
    EXPECT_EQ(val, def_val);

    val = 0;
    ASSERT_EQ(p->get("Single_Double.POSITIVE_MAX_DOUBLE", val, def_val, -DBL_MAX, DBL_MAX), Util::IniParser::OK);
    EXPECT_EQ(val, DBL_MAX);

    val = 0;
    ASSERT_EQ(p->get("Single_Double.NEGATIVE_MAX_DOUBLE", val, def_val, -DBL_MAX, DBL_MAX), Util::IniParser::OK);
    EXPECT_EQ(val, -DBL_MAX);

    val = 0;
    ASSERT_EQ(p->get("Single_Double.LARGER_THAN_MAX_DOUBLE", val, def_val, -DBL_MAX, DBL_MAX), Util::IniParser::VALUE_TYPE_ERR);
    EXPECT_EQ(val, def_val);

    // test min
    val = 0;
    ASSERT_EQ(p->get("Single_Double.DOUBLE_POSITIVE", val, def_val, -5.0, 5.0), Util::IniParser::VALUE_RANGE_ERR);
    EXPECT_EQ(val, def_val);

    val = 0;
    ASSERT_EQ(p->get("Single_Double.POSITIVE_MIN_DOUBLE", val, def_val, -DBL_MAX, DBL_MAX), Util::IniParser::OK);
    EXPECT_EQ(val, DBL_MIN);

    val = 0;
    ASSERT_EQ(p->get("Single_Double.NEGATIVE_MIN_DOUBLE", val, def_val, -DBL_MAX, DBL_MAX), Util::IniParser::OK);
    EXPECT_EQ(val, -DBL_MIN);

    //TYPE ERR
    ASSERT_EQ(p->get("String.STRING_NORMAL", val, def_val, -DBL_MAX, DBL_MAX), Util::IniParser::VALUE_TYPE_ERR);
    EXPECT_EQ(val, def_val);
}
TEST_F(TestIniParser, get_double_array)
{
    vector<double> val;
    vector<double> def_val = {1.1, 2.2, 3.3};
    ASSERT_EQ(p->get("Array_Double.A_DOUBLE_3", val, def_val, -DBL_MAX, DBL_MAX), Util::IniParser::OK);
    EXPECT_EQ(val[0], -10.1);
    EXPECT_EQ(val[1], 0);
    EXPECT_EQ(val[2], 10.1);

    ASSERT_EQ(p->get("Array_Double.A_DOUBLE_3_BLANK", val, def_val, -DBL_MAX, DBL_MAX), Util::IniParser::OK);
    EXPECT_EQ(val[0], -10.1);
    EXPECT_EQ(val[1], 0);
    EXPECT_EQ(val[2], 10.1);

    //invalid filename
    ASSERT_EQ(p_err->get("Array_Double.A_DOUBLE_3_BLANK", val, def_val, -DBL_MAX, DBL_MAX), Util::IniParser::FILE_ERR);
    EXPECT_EQ(val[0], def_val[0]);
    EXPECT_EQ(val[1], def_val[1]);
    EXPECT_EQ(val[2], def_val[2]);

    // invalid VALUE
    ASSERT_EQ(p->get("Empty.ONLY_KEY", val, def_val, -DBL_MAX, DBL_MAX), Util::IniParser::INI_VECTOR_FORMAT_ERR);
    EXPECT_EQ(val[0], def_val[0]);
    EXPECT_EQ(val[1], def_val[1]);
    EXPECT_EQ(val[2], def_val[2]);

    // invalid KEY
    ASSERT_EQ(p->get("Array_Double.NO_SUCH_KEY", val, def_val, -DBL_MAX, DBL_MAX), Util::IniParser::READ_ERR);
    EXPECT_EQ(val[0], def_val[0]);
    EXPECT_EQ(val[1], def_val[1]);
    EXPECT_EQ(val[2], def_val[2]);

    // invalid SECTION
    ASSERT_EQ(p->get("NO_SUCH_SECTION.NO_SUCH_KEY", val, def_val, -DBL_MAX, DBL_MAX), Util::IniParser::READ_ERR);
    EXPECT_EQ(val[0], def_val[0]);
    EXPECT_EQ(val[1], def_val[1]);
    EXPECT_EQ(val[2], def_val[2]);

    // 读取元素数量超过默认值
    ASSERT_EQ(p->get("Array_Double.A_DOUBLE_4", val, def_val, -DBL_MAX, DBL_MAX), Util::IniParser::DEFAULT_LEN_NOT_MACTH);
    EXPECT_EQ(val[0], 0.0);
    EXPECT_EQ(val[1], 1.0);
    EXPECT_EQ(val[2], 2.0);

    // 读取元素数量少于默认值
    ASSERT_EQ(p->get("Array_Double.A_DOUBLE_2", val, def_val, -DBL_MAX, DBL_MAX), Util::IniParser::DEFAULT_LEN_NOT_MACTH);
    EXPECT_EQ(val[0], 0.0);
    EXPECT_EQ(val[1], 1.0);
    EXPECT_EQ(val[2], def_val[2]);

    // Vector格式不满足以'{}'为开始和结束
    ASSERT_EQ(p->get("Array_Double.A_DOUBLE_HALF", val, def_val, -DBL_MAX, DBL_MAX), Util::IniParser::INI_VECTOR_FORMAT_ERR);
    EXPECT_EQ(val[0], def_val[0]);
    EXPECT_EQ(val[1], def_val[1]);
    EXPECT_EQ(val[2], def_val[2]);

    //test range
    ASSERT_EQ(p->get("Array_Double.A_DOUBLE_3", val, def_val, -5.0, 5.0), Util::IniParser::VALUE_RANGE_ERR);
    EXPECT_EQ(val[0], def_val[0]);
    EXPECT_EQ(val[1], 0);
    EXPECT_EQ(val[2], def_val[2]);

    ASSERT_EQ(p->get("Array_Double.A_DOUBLE_MAX_3", val, def_val, -DBL_MAX, DBL_MAX), Util::IniParser::OK);
    EXPECT_EQ(val[0], DBL_MAX);
    EXPECT_EQ(val[1], -DBL_MAX);
    EXPECT_EQ(val[2], 2);

    ASSERT_EQ(p->get("Array_Double.A_DOUBLE_LARGER_THAN_MAX_3", val, def_val, -DBL_MAX, DBL_MAX), Util::IniParser::VALUE_TYPE_ERR);
    EXPECT_EQ(val[0], def_val[0]);
    EXPECT_EQ(val[1], def_val[1]);
    EXPECT_EQ(val[2], 2);

    //test range
    ASSERT_EQ(p->get("Array_Double.A_DOUBLE_3", val, def_val, -5.0, 5.0), Util::IniParser::VALUE_RANGE_ERR);
    EXPECT_EQ(val[0], def_val[0]);
    EXPECT_EQ(val[1], 0);
    EXPECT_EQ(val[2], def_val[2]);

    ASSERT_EQ(p->get("Array_Double.A_DOUBLE_MAX_3", val, def_val, -DBL_MAX, DBL_MAX), Util::IniParser::OK);
    EXPECT_EQ(val[0], DBL_MAX);
    EXPECT_EQ(val[1], -DBL_MAX);
    EXPECT_EQ(val[2], 2);

    //test type err
    ASSERT_EQ(p->get("Array_String.A_STRING_3_NORMAL", val, def_val, -DBL_MAX, DBL_MAX), Util::IniParser::VALUE_TYPE_ERR);
    EXPECT_EQ(val[0], def_val[0]);
    EXPECT_EQ(val[1], def_val[1]);
    EXPECT_EQ(val[2], def_val[2]);
}

TEST_F(TestIniParser, get_bool)
{
    bool val;
    bool def_val = false;
    val = 0;
    ASSERT_EQ(p->get("Single_Bool.INT_POSITIVE", val, def_val), Util::IniParser::OK);
    EXPECT_EQ(val, true);

    val = 0;
    ASSERT_EQ(p->get("Single_Bool.INT_NEGATIVE", val, def_val), Util::IniParser::OK);
    EXPECT_EQ(val, true);

    val = 1;
    ASSERT_EQ(p->get("Single_Bool.INT_ZERO", val, def_val), Util::IniParser::OK);
    EXPECT_EQ(val, false);

    //invalid filename
    ASSERT_EQ(p_err->get("Single_Bool.INT_ZERO", val, def_val), Util::IniParser::FILE_ERR);
    EXPECT_EQ(val, def_val);

    // invalid VALUE ,return defval
    val = 1;
    ASSERT_EQ(p->get("Empty.ONLY_KEY", val, def_val), Util::IniParser::VALUE_TYPE_ERR);
    EXPECT_EQ(val, def_val);

    // invalid KEY
    val = 1;
    ASSERT_EQ(p->get("Single_Int.NO_SUCH_KEY", val, def_val), Util::IniParser::READ_ERR);
    EXPECT_EQ(val, def_val);

    // invalid SECTION
    val = 1;
    ASSERT_EQ(p->get("NO_SUCH_SECTION.NO_SUCH_KEY", val, def_val), Util::IniParser::READ_ERR);
    EXPECT_EQ(val, def_val);

    //TYPE ERR
    val = 1;
    ASSERT_EQ(p->get("String.STRING_NORMAL", val, def_val), Util::IniParser::VALUE_TYPE_ERR);
    EXPECT_EQ(val, def_val);

    val = 1;
    ASSERT_EQ(p->get("Single_Bool.DOUBLE_LESS_THAN_ONE", val, def_val), Util::IniParser::VALUE_TYPE_ERR);
    EXPECT_EQ(val, def_val);

    val = 0;
    ASSERT_EQ(p->get("Single_Bool.DOUBLE_LARGER_THAN_ONE", val, def_val), Util::IniParser::VALUE_TYPE_ERR);
    EXPECT_EQ(val, def_val);
}
TEST_F(TestIniParser, get_bool_array)
{
    vector<bool> val;
    vector<bool> def_val = {false, false, false};
    ASSERT_EQ(p->get("Array_Bool.A_INT_3", val, def_val), Util::IniParser::OK);
    EXPECT_EQ(val[0], true);
    EXPECT_EQ(val[1], false);
    EXPECT_EQ(val[2], true);

    ASSERT_EQ(p->get("Array_Bool.A_INT_3_BLANK", val, def_val), Util::IniParser::OK);
    EXPECT_EQ(val[0], true);
    EXPECT_EQ(val[1], false);
    EXPECT_EQ(val[2], true);

    //invalid filename
    ASSERT_EQ(p_err->get("Array_Bool.A_INT_3_BLANK", val, def_val), Util::IniParser::FILE_ERR);
    EXPECT_EQ(val[0], def_val[0]);
    EXPECT_EQ(val[1], def_val[1]);
    EXPECT_EQ(val[2], def_val[2]);

    // invalid VALUE
    ASSERT_EQ(p->get("Array_Bool.NO_SUCH_KEY", val, def_val), Util::IniParser::READ_ERR);
    EXPECT_EQ(val[0], def_val[0]);
    EXPECT_EQ(val[1], def_val[1]);
    EXPECT_EQ(val[2], def_val[2]);

    // invalid KEY
    ASSERT_EQ(p->get("Array_Bool.NO_SUCH_KEY", val, def_val), Util::IniParser::READ_ERR);
    EXPECT_EQ(val[0], def_val[0]);
    EXPECT_EQ(val[1], def_val[1]);
    EXPECT_EQ(val[2], def_val[2]);

    // invalid SECTION
    ASSERT_EQ(p->get("NO_SUCH_SECTION.NO_SUCH_KEY", val, def_val), Util::IniParser::READ_ERR);
    EXPECT_EQ(val[0], def_val[0]);
    EXPECT_EQ(val[1], def_val[1]);
    EXPECT_EQ(val[2], def_val[2]);

    // 读取元素数量超过默认值
    ASSERT_EQ(p->get("Array_Bool.A_INT_4", val, def_val), Util::IniParser::DEFAULT_LEN_NOT_MACTH);
    EXPECT_EQ(val[0], false);
    EXPECT_EQ(val[1], true);
    EXPECT_EQ(val[2], true);

    // 读取元素数量少于默认值
    ASSERT_EQ(p->get("Array_Bool.A_INT_2", val, def_val), Util::IniParser::DEFAULT_LEN_NOT_MACTH);
    EXPECT_EQ(val[0], true);
    EXPECT_EQ(val[1], false);
    EXPECT_EQ(val[2], def_val[2]);

    // Vector格式不满足以'{}'为开始和结束
    ASSERT_EQ(p->get("Array_Bool.A_INT_HALF", val, def_val), Util::IniParser::INI_VECTOR_FORMAT_ERR);
    EXPECT_EQ(val[0], def_val[0]);
    EXPECT_EQ(val[1], def_val[1]);
    EXPECT_EQ(val[2], def_val[2]);

    //test type err
    ASSERT_EQ(p->get("Array_String.A_STRING_3_NORMAL", val, def_val), Util::IniParser::VALUE_TYPE_ERR);
    EXPECT_EQ(val[0], def_val[0]);
    EXPECT_EQ(val[1], def_val[1]);
    EXPECT_EQ(val[2], def_val[2]);

    ASSERT_EQ(p->get("Array_Double.A_DOUBLE_3", val, def_val), Util::IniParser::VALUE_TYPE_ERR);
    EXPECT_EQ(val[0], def_val[0]);
    EXPECT_EQ(val[1], false);
    EXPECT_EQ(val[2], def_val[2]);
}

TEST_F(TestIniParser, get_string)
{
    string val = "0";
    string def_val = "default";

    ASSERT_EQ(p->get("String.STRING_REGEX", val, def_val), Util::IniParser::OK);
    EXPECT_EQ(val, "^1210(f[0-1][0-1])?00[0-1][0-3]$");

    val = "0";
    ASSERT_EQ(p->get("String.STRING_NORMAL", val, def_val), Util::IniParser::OK);
    EXPECT_EQ(val, "normal");

    val = "0";
    ASSERT_EQ(p->get("String.STRING_AFTER_EQUAL", val, def_val), Util::IniParser::OK);
    EXPECT_EQ(val, "normal");

    // Empty VALUE
    val = "0";
    ASSERT_EQ(p->get("Empty.ONLY_KEY", val, def_val), Util::IniParser::OK);
    EXPECT_EQ(val, "");

    //invalid filename
    ASSERT_EQ(p_err->get("String.STRING_AFTER_EQUAL", val, def_val), Util::IniParser::FILE_ERR);
    EXPECT_EQ(val, def_val);

    // invalid KEY
    val = "0";
    ASSERT_EQ(p->get("Single_Int.NO_SUCH_KEY", val, def_val), Util::IniParser::READ_ERR);
    EXPECT_EQ(val, def_val);

    // invalid SECTION
    val = "0";
    ASSERT_EQ(p->get("NO_SUCH_SECTION.NO_SUCH_KEY", val, def_val), Util::IniParser::READ_ERR);
    EXPECT_EQ(val, def_val);

    val = "0";
    ASSERT_EQ(p->get("String.STRING_WITH_BLANK", val, def_val), Util::IniParser::OK);
    EXPECT_EQ(val, "just always keep amazing");
}
TEST_F(TestIniParser, get_string_array)
{
    vector<string> val;
    vector<string> def_val = {"default1", "default2", "default3"};
    ASSERT_EQ(p->get("Array_String.A_STRING_3_NORMAL", val, {"jaka", "jaka", "jaka"}), Util::IniParser::OK);
    EXPECT_EQ(val[0], "normal1");
    EXPECT_EQ(val[1], "normal2");
    EXPECT_EQ(val[2], "normal3");

    //invalid filename
    ASSERT_EQ(p_err->get("String.STRING_AFTER_EQUAL", val, def_val), Util::IniParser::FILE_ERR);
    EXPECT_EQ(val[0], def_val[0]);
    EXPECT_EQ(val[1], def_val[1]);
    EXPECT_EQ(val[2], def_val[2]);

    // 元素数量多于默认值
    ASSERT_EQ(p->get("Array_String.A_STRING_4_NORMAL", val, def_val), Util::IniParser::DEFAULT_LEN_NOT_MACTH);
    EXPECT_EQ(val[0], "normal1");
    EXPECT_EQ(val[1], "normal2");
    EXPECT_EQ(val[2], "normal3");
    // 元素数量少于默认值
    ASSERT_EQ(p->get("Array_String.A_STRING_2_NORMAL", val, def_val), Util::IniParser::DEFAULT_LEN_NOT_MACTH);
    EXPECT_EQ(val[0], "normal1");
    EXPECT_EQ(val[1], "normal2");
    EXPECT_EQ(val[2], def_val[2]);

    // Vector格式不满足以'{}'为开始和结束
    ASSERT_EQ(p->get("Array_String.A_STRING_3_HALF", val, def_val), Util::IniParser::INI_VECTOR_FORMAT_ERR);
    EXPECT_EQ(val[0], def_val[0]);
    EXPECT_EQ(val[1], def_val[1]);
    EXPECT_EQ(val[2], def_val[2]);

    // invalid VALUE
    ASSERT_EQ(p->get("Empty.ONLY_KEY", val, def_val), Util::IniParser::INI_VECTOR_FORMAT_ERR);
    EXPECT_EQ(val[0], def_val[0]);
    EXPECT_EQ(val[1], def_val[1]);
    EXPECT_EQ(val[2], def_val[2]);

    // invalid KEY
    ASSERT_EQ(p->get("Array_String.NO_SUCH_KEY", val, def_val), Util::IniParser::READ_ERR);
    EXPECT_EQ(val[0], def_val[0]);
    EXPECT_EQ(val[1], def_val[1]);
    EXPECT_EQ(val[2], def_val[2]);

    // invalid SECTION
    ASSERT_EQ(p->get("NO_SUCH_SECTION.NO_SUCH_KEY", val, def_val), Util::IniParser::READ_ERR);
    EXPECT_EQ(val[0], def_val[0]);
    EXPECT_EQ(val[1], def_val[1]);
    EXPECT_EQ(val[2], def_val[2]);

    // TEST BLANK IN VALUE
    ASSERT_EQ(p->get("Array_String.A_STRING_3_WITH_BLANK", val, def_val), Util::IniParser::OK);
    EXPECT_EQ(val[0], " just always keep amazing ");
    EXPECT_EQ(val[1], " just always keep amazing2 ");
    EXPECT_EQ(val[2], " just always keep amazing3 ");
}

TEST_F(TestIniParser, set_int_value)
{
    int read_value = 0;
    int set_value = 123;
    unique_ptr<Util::IniParser> p_rw;
    unique_ptr<Util::IniParser> p_read;
    p_rw = make_unique<IniParser>(filename.c_str());
    ASSERT_EQ(p_rw->get("WriteTest.key", read_value, 0), Util::IniParser::OK);
    EXPECT_EQ(read_value, 1);
    // 测试设置int类型的值
    EXPECT_EQ(0, p_rw->set("WriteTest.key", set_value));
    // 此时文件未更新,验证文件内容
    p_read = make_unique<IniParser>(filename.c_str());
    ASSERT_EQ(p_read->get("WriteTest.key", read_value, 0), Util::IniParser::OK);
    EXPECT_EQ(read_value, 1);
    p_rw.reset();//此时文件更新
    p_read.reset();//此实例未set，文件内容应为p_rw
    p_read = make_unique<IniParser>(filename.c_str());
    ASSERT_EQ(p_read->get("WriteTest.key", read_value, 0), Util::IniParser::OK);
    EXPECT_EQ(read_value, set_value);
}

TEST_F(TestIniParser, set_double_value)
{
    double read_value = 0.0;
    double set_value = 123.123;
    unique_ptr<Util::IniParser> p_rw;
    unique_ptr<Util::IniParser> p_read;
    p_rw = make_unique<IniParser>(filename.c_str());
    ASSERT_EQ(p_rw->get("WriteTest.key", read_value, 0.0, -DBL_MAX, DBL_MAX), Util::IniParser::OK);
    EXPECT_EQ(read_value, 1.0);
    // 测试设置double类型的值
    EXPECT_EQ(0, p_rw->set("WriteTest.key", set_value));
    p_read = make_unique<IniParser>(filename.c_str());
    ASSERT_EQ(p_read->get("WriteTest.key", read_value, 0.0, -DBL_MAX, DBL_MAX), Util::IniParser::OK);
    EXPECT_EQ(read_value, 1.0);
    p_rw.reset();//此时文件更新
    p_read.reset();//此实例未set，文件内容应为p_rw
    // 验证文件内容
    p_read = make_unique<IniParser>(filename.c_str());
    ASSERT_EQ(p_read->get("WriteTest.key", read_value, 0.0, -DBL_MAX, DBL_MAX), Util::IniParser::OK);
    EXPECT_EQ(read_value, set_value);
}

TEST_F(TestIniParser, set_bool_value)
{
    bool read_value = false;
    bool set_value = false;
    unique_ptr<Util::IniParser> p_rw;
    unique_ptr<Util::IniParser> p_read;
    p_rw = make_unique<IniParser>(filename.c_str());
    ASSERT_EQ(p_rw->get("WriteTest.key", read_value, false), Util::IniParser::OK);
    EXPECT_EQ(read_value, true);
    // 测试设置bool类型的值
    EXPECT_EQ(0, p_rw->set("WriteTest.key", set_value));
    p_read = make_unique<IniParser>(filename.c_str());
    ASSERT_EQ(p_read->get("WriteTest.key", read_value, false), Util::IniParser::OK);
    EXPECT_EQ(read_value, true);
    p_rw.reset();//此时文件更新
    p_read.reset();//此实例未set，文件内容应为p_rw
    // 验证文件内容
    p_read = make_unique<IniParser>(filename.c_str());
    ASSERT_EQ(p_read->get("WriteTest.key", read_value, true), Util::IniParser::OK);
    EXPECT_EQ(read_value, set_value);
}

TEST_F(TestIniParser, set_string_int)
{
    string read_value = "0";
    string set_value = "123";
    unique_ptr<Util::IniParser> p_rw;
    unique_ptr<Util::IniParser> p_read;
    p_rw = make_unique<IniParser>(filename.c_str());
    ASSERT_EQ(p_rw->get("WriteTest.key", read_value, "default"), Util::IniParser::OK);
    EXPECT_EQ(read_value, "1");
    // 测试设置string类型的值
    EXPECT_EQ(0, p_rw->set("WriteTest.key", set_value));
    p_read = make_unique<IniParser>(filename.c_str());
    ASSERT_EQ(p_read->get("WriteTest.key", read_value, "default"), Util::IniParser::OK);
    EXPECT_EQ(read_value, "1");
    p_rw.reset();//此时文件更新
    p_read.reset();//此实例未set，文件内容应为p_rw
    // 验证文件内容
    p_read = make_unique<IniParser>(filename.c_str());
    ASSERT_EQ(p_read->get("WriteTest.key", read_value, "default"), Util::IniParser::OK);
    EXPECT_EQ(read_value, set_value);
}

TEST_F(TestIniParser, set_int_array_value)
{
    vector<int> read_value = {0, 0, 0};
    vector<int> set_value = {1, 2, 3};
    vector<int> def_value = {0, 0, 1};
    unique_ptr<Util::IniParser> p_rw;
    p_rw = make_unique<IniParser>(filename.c_str());
    ASSERT_EQ(p_rw->get("WriteTest.array_key", read_value, {0, 0, 0}), Util::IniParser::OK);
    EXPECT_EQ(read_value[0], def_value[0]);
    EXPECT_EQ(read_value[1], def_value[1]);
    EXPECT_EQ(read_value[2], def_value[2]);
    // 测试设置int_array类型的值
    EXPECT_EQ(0, p_rw->set("WriteTest.array_key", set_value));
    p_rw.reset();//此时文件更新
    // 验证文件内容
    IniParser p_read(filename.c_str());
    ASSERT_EQ(p_read.get("WriteTest.array_key", read_value, {0, 0, 0}), Util::IniParser::OK);
    EXPECT_EQ(read_value[0], set_value[0]);
    EXPECT_EQ(read_value[1], set_value[1]);
    EXPECT_EQ(read_value[2], set_value[2]);
}

TEST_F(TestIniParser, set_double_array_value)
{
    vector<double> read_value = {0.0, 0.0, 0.0};
    vector<double> set_value = {1.1, 2.2, 3.3};
    vector<double> def_value = {0.0, 0.0, 1.0};
    unique_ptr<Util::IniParser> p_rw;
    p_rw = make_unique<IniParser>(filename.c_str());
    ASSERT_EQ(p_rw->get("WriteTest.array_key", read_value, {0.0, 0.0, 0.0}, -DBL_MAX, DBL_MAX), Util::IniParser::OK);
    EXPECT_EQ(read_value[0], def_value[0]);
    EXPECT_EQ(read_value[1], def_value[1]);
    EXPECT_EQ(read_value[2], def_value[2]);
    // 测试设置double_array类型的值
    EXPECT_EQ(0, p_rw->set("WriteTest.array_key", set_value));
    p_rw.reset();//此时文件更新
    // 验证文件内容
    IniParser p_read(filename.c_str());
    ASSERT_EQ(p_read.get("WriteTest.array_key", read_value, {0.0, 0.0, 0.0}, -DBL_MAX, DBL_MAX), Util::IniParser::OK);
    EXPECT_EQ(read_value[0], set_value[0]);
    EXPECT_EQ(read_value[1], set_value[1]);
    EXPECT_EQ(read_value[2], set_value[2]);
}

TEST_F(TestIniParser, set_bool_array_value)
{
    vector<bool> read_value = {0, 0, 0};
    vector<bool> set_value = {1, 1, 0};
    vector<bool> def_value = {0, 0, 1};
    unique_ptr<Util::IniParser> p_rw;
    p_rw = make_unique<IniParser>(filename.c_str());
    ASSERT_EQ(p_rw->get("WriteTest.array_key", read_value, {false, false, false}), Util::IniParser::OK);
    EXPECT_EQ(read_value[0], def_value[0]);
    EXPECT_EQ(read_value[1], def_value[1]);
    EXPECT_EQ(read_value[2], def_value[2]);
    // 测试设置bool_array类型的值
    EXPECT_EQ(0, p_rw->set("WriteTest.array_key", set_value));
    p_rw.reset();//此时文件更新
    // 验证文件内容
    IniParser p_read(filename.c_str());
    ASSERT_EQ(p_read.get("WriteTest.array_key", read_value, {false, false, false}), Util::IniParser::OK);
    EXPECT_EQ(read_value[0], set_value[0]);
    EXPECT_EQ(read_value[1], set_value[1]);
    EXPECT_EQ(read_value[2], set_value[2]);
}

TEST_F(TestIniParser, set_autocreate_file)
{
    vector<bool> read_value = {0, 0, 0};
    vector<bool> set_value = {1, 1, 0};
    int read_value2 = 0;
    int set_value2 = 123;
    unique_ptr<Util::IniParser> p_rw;
    p_rw = make_unique<IniParser>(none_filename.c_str());
    ASSERT_EQ(p_rw->get("WriteTest.array_key", read_value, {false, false, false}), Util::IniParser::FILE_ERR);
    ASSERT_EQ(p_rw->get("WriteTest.key", read_value2, 0), Util::IniParser::FILE_ERR);
    // 测试设置bool_array类型的值
    EXPECT_EQ(0, p_rw->set("WriteTest.array_key", set_value));
    // 测试设置int类型的值
    EXPECT_EQ(0, p_rw->set("WriteTest.key", set_value2));
    p_rw.reset();//此时文件更新
    // 验证文件内容
    IniParser p_read(none_filename.c_str());
    ASSERT_EQ(p_read.get("WriteTest.array_key", read_value, {false, false, false}), Util::IniParser::OK);
    EXPECT_EQ(read_value[0], set_value[0]);
    EXPECT_EQ(read_value[1], set_value[1]);
    EXPECT_EQ(read_value[2], set_value[2]);
    ASSERT_EQ(p_read.get("WriteTest.key", read_value2, 0), Util::IniParser::OK);
    EXPECT_EQ(read_value2, set_value2);
    // 尝试删除文件
    ASSERT_EQ(std::remove(none_filename.c_str()), 0);
}